// spa页面不能刷新的：hash，history api操作(页面不刷新，路由变化)

// URL发生变化，显示对应的内容
// 实现router-view组件   占位容器
// 数据响应式的

// 为什么router-view和vue是强相关的？ 是一个vue里的插件，对vue的响应式有一个强依赖

// Vue.use的是一个插件，表示这个对象或方法必须实现一个install的方法 
let Vue
class VueRouter {
  constructor(options) {
    // new的时候会传一个选项进来
    this.options = options

    // 数据响应式，current必须是响应式的，这样他变化，使用的组件就会重新render
    // 如何创建一个响应式
    // 1、借鸡生蛋，利用vue的响应式，  new Vue({data:{current:''}})
    // 2、Vue.util.defineReactive(obj,'current')给对象设置一个响应式的属性
    // this.current = window.location.hash.slice(1)||''
    // Vue.util.defineReactive就是vue里对对象做响应式的方法， 
    Vue.util.defineReactive(this, 'current', window.location.hash.slice(1) || '')
    // 监控URL变化hash(hashchange),history(popstate)
    window.addEventListener('hashchange', () => {
      this.current = window.location.hash.slice(1)
    })
  }
}
// 插件要实现一个install的方法
VueRouter.install = function (_Vue) {
  // 在使用的时候，是先install，然后再new的实例

  Vue = _Vue

  // 注册router实例
  // 通过全局混入：
  Vue.mixin({
    // 每一个beforeCreate都会执行
    beforeCreate() {
      // 仅在根组件创建的时候执行一次
      if (this.$options.router) {
        // console.log(this.$options.router, '============');
        // 通过this.options获取到当前的这个选项，在通过router属性得到这个实例
        Vue.prototype.$router = this.$options.router
      }
    }
  })


  //  注册两个组件，router-view,link
  Vue.component('router-view', {
    // 开发环境不带编译器，不能写template，只能是render
    // 可以使用jsx--兼容性不好
    render(h) {
      // 获取URL，做路由映射关系
      // window.location.hash
      let { current, options } = this.$router
      let component = null
      let route = options.routes.find(route => route.path === current)
      // console.log(current, options, '============');
      if (route) {
        component = route.component
      }
      return h(component)
    }
  })
  Vue.component('router-link', {
    props: {
      to: {
        type: String,
        required: true
        // default:''
      }
    },
    render(h) {
      return h('a', { attrs: { href: '#' + this.to } }, this.$slots.default)
    }
  })
}
export default VueRouter